跳到主要内容

Rust 特征

阐述

特征定义了一组可以被共享的行为,只要实现了特征,你就能使用这组行为。定义特征时,需要定义方法的签名,但是不需要实现。

为类型实现特征的时候,类型和特征至少要有一个是在当前作用域里定义的。

默认实现

可以在特征的定义中就包含一个实现,这样其他类型可以获得一个默认的实现,或者也可以重载这个实现。

关联类型

TODO

默认类型参数

TODO

特征定义中的特征约束

TODO

实例

性质

特征约束

Rust 泛型函数中可以限制类型为具有某个特征的类型:

pub fn notify<T: Summary>(item: &T) {
println!("Breaking news! {}", item.summarize());
}

pub fn notify(item: &impl Summary) {
println!("Breaking news! {}", item.summarize());
}

特征的约束可以是多重的:

pub fn notify(item: &(impl Summary + Display)) {}
pub fn notify<T: Summary + Display>(item: &T) {}

特征的约束也可以用 where 的方式后置:

fn some_function<T, U>(t: &T, u: &U) -> i32
where T: Display + Clone,
U: Clone + Debug
{}

特征约束可以用来给部分类型实现方法:

use std::fmt::Display;

struct Pair<T> {
x: T,
y: T,
}

impl<T> Pair<T> {
fn new(x: T, y: T) -> Self {
Self {
x,
y,
}
}
}

impl<T: Display + PartialOrd> Pair<T> {
fn cmp_display(&self) {
if self.x >= self.y {
println!("The largest member is x = {}", self.x);
} else {
println!("The largest member is y = {}", self.y);
}
}
}

特征返回

可以把特征作为函数的返回值,避免写出非常复杂的类型:

fn returns_summarizable() -> impl Summary {
Weibo {
username: String::from("sunface"),
content: String::from(
"m1 max太厉害了,电脑再也不会卡",
)
}
}

相关内容

调用同名方法

TODO

绕过孤儿规则

可以为一个元组结构体来定义特征,这个结构体是对原来的类型的封装,这样就避免了孤儿规则的限制:

struct Wrapper(Vec<String>);

参考文献